//Michele Gregori 2009 miclegr@gmail.com

#include "dualQuaternionCmd.h"

MStatus dqDeformerCmd::doIt(const MArgList &arg){
	
	MGlobal::getActiveSelectionList(sel);
	return this->redoIt();
}
	
MStatus dqDeformerCmd::redoIt(){

	MObject skinObj,dqObj;
	sel.getDependNode(0,skinObj);
	//sel.getDependNode(1,dqObj);
	dgModCreate=new MDGModifier;
	dgModCon=new MDGModifier;
	dgModDisc=new MDGModifier;
	dqObj=dgModCreate->createNode("dqDeformer");
	MFnDependencyNode skinFn(skinObj);
	dgModCreate->doIt();
	MFnDependencyNode dqFn(dqObj);	
	
	MString attr="weightList";
	
	MPlug skinPlug=skinFn.findPlug(attr);
	MPlug dqPlug=dqFn.findPlug(attr);
	MPlug skinPlugW=skinFn.findPlug("weights");
	int num=skinFn.findPlug("matrix").numElements();
	int numVtx=skinPlugW.numElements();
	for(int x=0;x<numVtx;x++){
		MPlug skinWeight=skinPlug.elementByLogicalIndex(x).child(0);
		MPlug dqWeight=dqPlug.elementByLogicalIndex(x).child(0);
		for(int y=0;y<num;y++){
			double w=skinWeight.elementByLogicalIndex(y).asDouble();
			dqWeight.elementByLogicalIndex(y).setValue(w);
		}
	}
	
	attr="lockWeights";
	skinPlug=skinFn.findPlug(attr);
	dqPlug=dqFn.findPlug(attr);
	num=skinPlug.numElements();
	MPlugArray array;
	for(int x=0;x<num;x++){
		MPlug skinMatN=skinPlug.elementByLogicalIndex(x);
		skinMatN.connectedTo(array,1,0);
		MPlug dqMatN=dqPlug.elementByLogicalIndex(x);
		dgModDisc->disconnect(array[0],skinMatN);
		dgModCon->connect(array[0],dqMatN);
	}
	
	attr="bindPreMatrix";
	skinPlug=skinFn.findPlug(attr);
	dqPlug=dqFn.findPlug(attr);
	num=skinPlug.numElements();
	for(int x=0;x<num;x++){
		MObject skinVal=skinPlug.elementByLogicalIndex(x).asMObject();
		MPlug bPl=dqPlug.elementByLogicalIndex(x);
		bPl.setValue(skinVal);
	}	
	
	attr="geomMatrix";
	skinPlug=skinFn.findPlug(attr);
	dqPlug=dqFn.findPlug(attr);
	MObject skinVal=skinPlug.asMObject();
	dqPlug.setValue(skinVal);
	
	attr="matrix";
	skinPlug=skinFn.findPlug(attr);
	dqPlug=dqFn.findPlug(attr);
	num=skinPlug.numElements();
	for(int x=0;x<num;x++){
		MPlug skinMatN=skinPlug.elementByLogicalIndex(x);
		skinMatN.connectedTo(array,1,0);
		MPlug dqMatN=dqPlug.elementByLogicalIndex(x);
		dgModDisc->disconnect(array[0],skinMatN);
		dgModCon->connect(array[0],dqMatN);
	}

	attr="paintTrans";
	skinPlug=skinFn.findPlug(attr);
	dqPlug=dqFn.findPlug(attr);
	skinPlug.connectedTo(array,1,0);
	if(array.length()>0){
		dgModDisc->disconnect(array[0],skinPlug);
		dgModCon->connect(array[0],dqPlug);
	}

	attr="outputGeometry";
	skinPlug=skinFn.findPlug(attr);
	dqPlug=dqFn.findPlug(attr);
	MPlug skP0=skinPlug.elementByLogicalIndex(0);
	MPlug dqP0=dqPlug.elementByLogicalIndex(0);
	skP0.connectedTo(array,0,1);
	dgModDisc->disconnect(skP0,array[0]);
	dgModCon->connect(dqP0,array[0]);
	
	attr="message";
	skinPlug=skinFn.findPlug(attr);
	dqPlug=dqFn.findPlug(attr);
	skinPlug.connectedTo(array,0,1);
	dgModDisc->disconnect(skinPlug,array[0]);
	dgModCon->connect(dqPlug,array[0]);
	
	attr="bindPose";
	skinPlug=skinFn.findPlug(attr);
	dqPlug=dqFn.findPlug(attr);
	skinPlug.connectedTo(array,1,0);
	dgModDisc->disconnect(array[0],skinPlug);
	dgModCon->connect(array[0],dqPlug);

	attr="input";
	skinPlug=skinFn.findPlug(attr).elementByLogicalIndex(0);
	dqPlug=dqFn.findPlug(attr).elementByLogicalIndex(0);
	MPlug skIs=skinPlug.child(0);
	MPlug skId=skinPlug.child(1);
	MPlug dqIs=dqPlug.child(0);
	MPlug dqId=dqPlug.child(1);
	skIs.connectedTo(array,1,0);
	dgModDisc->disconnect(array[0],skIs);
	dgModCon->connect(array[0],dqIs);/*
	skId.connectedTo(array,1,0);
	dgModDisc->disconnect(array[0],skId);
	dgModCon->connect(array[0],dqId);*/
	
	dgModDisc->doIt();
	dgModCon->doIt();
	
	setResult(dqFn.name());
	return MS::kSuccess;
}

MStatus dqDeformerCmd::undoIt(){
	dgModCon->undoIt();
	delete dgModCon;
	dgModDisc->undoIt();
	delete dgModDisc;
	dgModCreate->undoIt();
	delete dgModCreate;
	return MS::kSuccess;	
}

